package com.kifas.service.dataaccess;

import java.util.Date;
import java.util.List;

import org.hibernate.SessionFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Repository;

import com.kifas.entity.PengirimanDetailEntity;
import com.kifas.entity.PengirimanEntity;
import com.kifas.entity.TransactionStokEntity;
import com.kifas.utils.TransactionReferencePopulator;

@Repository
public class PengirimanDao {

	@Autowired
	private SessionFactory sessionFactory;

	private final static String ALL_PENGIRIMAN = "from PengirimanEntity kirim left join fetch kirim.pengirimanDetails ";
	private final static String PENGIRIMAN_BY_ID = ALL_PENGIRIMAN + " where kirim.idPengiriman = :idPengiriman ";
	private final static String PENGIRIMAN_BY_ID_PENJUALAN = ALL_PENGIRIMAN + " where kirim.idPenjualan = :idPenjualan ";
	private final static String PENGIRIMAN_BY_LIST_ID_PENJUALAN = ALL_PENGIRIMAN + " where kirim.idPenjualan in :idPenjualans ";
	private final static String PENGIRIMAN_BY_TANGGAL_KIRIM_RANGE = ALL_PENGIRIMAN
			+ " where kirim.tanggalKirim >= :startDate and kirim.tanggalKirim <= :endDate ";
	private final static String PENGIRIMAN_LATEST_BY_PENJUALAN = ALL_PENGIRIMAN + " where kirim.idPenjualan = :idPenjualan order by kirim.tanggalKirim";
	private final static String PENGIRIMAN_UNRECEIVED = ALL_PENGIRIMAN + " where kirim.tanggalTerima = null ";
	private final static String PENGIRIMAN_RECEIVED = ALL_PENGIRIMAN + " where kirim.tanggalTerima != null ";

	@SuppressWarnings("unchecked")
	public List<PengirimanEntity> getPengirimans() {
		return sessionFactory.getCurrentSession().createQuery(ALL_PENGIRIMAN).list();
	}

	public PengirimanEntity getPengirimanById(Long id) {
		return (PengirimanEntity) sessionFactory.getCurrentSession().createQuery(PENGIRIMAN_BY_ID).setParameter("idPengiriman", id).uniqueResult();
	}

	public PengirimanEntity getLatestPengirimanByIdPenjualan(Long idPenjualan) {
		@SuppressWarnings("unchecked")
		List<PengirimanEntity> list = sessionFactory.getCurrentSession().createQuery(PENGIRIMAN_LATEST_BY_PENJUALAN).setParameter("idPenjualan", idPenjualan).list();
		if(list.size() > 0)
			return list.get(0);
		else
			return null;
	}

	public void insert(PengirimanEntity pengiriman) throws Exception {
		if (sessionFactory.getCurrentSession().get(PengirimanEntity.class, pengiriman) == null) sessionFactory.getCurrentSession().save(pengiriman);
		for (PengirimanDetailEntity detail : pengiriman.getPengirimanDetails()) {
			if (sessionFactory.getCurrentSession().get(PengirimanDetailEntity.class, detail) == null) {
				sessionFactory.getCurrentSession().save(detail);
				TransactionStokEntity transaction = new TransactionStokEntity();
				TransactionReferencePopulator referencePopulator = new TransactionReferencePopulator();
				String hashString = referencePopulator.populatePengirimanHash(pengiriman.getNoPengiriman(), pengiriman.getTanggalKirim(),
						String.valueOf(pengiriman.getIdPenjualan()), String.valueOf(detail.getGudang().getIdGudang()),
						String.valueOf(detail.getBarang().getIdBarang()), detail.getBulanKadaluarsa(), String.valueOf(detail.getQty()));
				transaction.setIdTransactionStok(null);
				transaction.setCanceled(false);
				transaction.setCount(false);
				transaction.setInputFlag(false);
				transaction.setQty(detail.getQty().longValue());
				transaction.setBulanKadaluarsa(detail.getBulanKadaluarsa());
				transaction.setTanggal(new Date());
				transaction.setReference(hashString);
				transaction.setIdBarang(String.valueOf(detail.getBarang().getIdBarang()));
				transaction.setIdGudang(String.valueOf(detail.getGudang().getIdGudang()));
				sessionFactory.getCurrentSession().save(transaction);
			}
		}
	}

	@SuppressWarnings("unchecked")
	public List<PengirimanEntity> getPengirimanByIdPenjualans(List<Long> idPenjualans) {
		return sessionFactory.getCurrentSession().createQuery(PENGIRIMAN_BY_LIST_ID_PENJUALAN).setParameter("idPenjualans", idPenjualans).list();
	}

	@SuppressWarnings("unchecked")
	public List<PengirimanEntity> getPengirimanByIdPenjualan(Long idPenjualan) {
		return sessionFactory.getCurrentSession().createQuery(PENGIRIMAN_BY_ID_PENJUALAN).setParameter("idPenjualan", idPenjualan).list();
	}

	@SuppressWarnings("unchecked")
	public List<PengirimanEntity> getPengirimansByDate(Date startDate, Date endDate) {
		return sessionFactory.getCurrentSession().createQuery(PENGIRIMAN_BY_TANGGAL_KIRIM_RANGE).setParameter("startDate", startDate)
				.setParameter("endDate", endDate).list();
	}

	@SuppressWarnings("unchecked")
	public List<PengirimanEntity> getUnreceivedPengirimans() {
		return sessionFactory.getCurrentSession().createQuery(PENGIRIMAN_UNRECEIVED).list();
	}

	@SuppressWarnings("unchecked")
	public List<PengirimanEntity> getReceivedPengirimans() {
		return sessionFactory.getCurrentSession().createQuery(PENGIRIMAN_RECEIVED).list();
	}
}
